/****************************************************************
 * I am the AC 130 vs Pirate game. I allow the user to control an 
 * AC130 gunship in the hunt for Modern day pirates. The player  
 * will be allowed to roam free across a section of ocean/coastline.  
 * In the water there will be four types of vessels: Merchant  
 * ships that the player must protect, Pirate ships that the player  
 * must identify and destroy, Fishing boats that look like Pirate  
 * ships that the player must not destroy, and Friendly Navy ships  
 * that can capture pirates for extra points. Time permitting there  
 * may also be ground targets to attack. 
 *
 * Key elements of this project will be the Player/AC130, the Ships,  
 * the ShipAI system, the collision grid, the debris controller, the  
 * Ground/Water, Clouds, and scoring system. This project will make  
 * use of an external text file to store useful game parameters,  
 * thus allowing us to play balance the game without recompiling  
 * the executable. 
 *****************************************************************
 * I am the Ship Controll class. I contain the array of all ships.
 * I have the funcitons, that spawn, update and maintain the ships 
 * int he game.
 *****************************************************************/


#include "ShipCtrl.h"

ShipCtrl::ShipCtrl(){
	for(int itor =0; itor< MAXSHIP; itor++){
		myShip[itor] = new Ship;
	}
}


ShipCtrl::~ShipCtrl(){

}


/// pull in external data
void ShipCtrl::Init(GameData * exgd, BulletCtrl * exBulletCtrl,
		CrashBin * exCrashBin)
{
	gd = exgd;
	myBulletCtrl = exBulletCtrl;
	myCrashBin = exCrashBin;
		// pass gd to ships
	for(int itor =0; itor < MAXSHIP; itor++){
		myShip[itor]->Init(gd);
	}
		// populate maxType and Bitmaps
	// read maxType
	maxType = gd->GetNum("maxShipType");
	for(int itor =0; itor < maxType; itor++){
		btmBmp[itor] = load_bitmap(	gd->GetStr("shpBtmBmp",itor), NULL);
		topBmp[itor] = load_bitmap(	gd->GetStr("shpTopBmp",itor), NULL);
	}

		// reset all ships
	Reset();
		
}

/// I am the reset function I set all ships in the array 
/// to sunk and unused
void ShipCtrl::Reset(){
	for(int itor =0; itor < MAXSHIP; itor++){
		myShip[itor]->sinkPhase = myShip[itor]->maxSinkPhase;
	}
}

/// I am the spawn function. I insert a ship into the world
/// at the specified location, of the indexed type, and who 
/// will follow the AI Path
void ShipCtrl::Spawn(Point * start, int type, int path){
	int index = -1;
		// find first available index
	for(int itor = 0; itor < MAXSHIP; itor++){
			// found unused ship
		if( myShip[itor]->sinkPhase == myShip[itor]->maxSinkPhase){
			index = itor;
			itor = MAXSHIP;	// end loop
		}
	}
	if(index < 0) return;	// failed to spawn
		// set Indexed ship to be alive
	myShip[index]->hp = 100;
	myShip[index]->sinkPhase = 0;
	myShip[index]->sinkTime = 0;
		// set ship's physical properties
	myShip[index]->center->Copy(start);
	myShip[index]->angleDlt = 5;
	myShip[index]->angle = path;
	myShip[index]->speedMax = 5;
	myShip[index]->speedDlt = 1;
	myShip[index]->speedCur = 0;
		// set ships AI values
	// 0-player, 1-merchant, 2-fisherman, 3-pirate
	myShip[index]->aiLoyalty = 3;
	// 0-navigate, 1-run, 2-attack, 3-go home, 4-hijacked, 5 derilict
	myShip[index]->aiMode = 0;	
	myShip[index]->navIndex = path;
		// import bitmaps
	myShip[index]->btmBmp = btmBmp[type];
	destroy_bitmap(myShip[index]->tempBmp);
	destroy_bitmap(myShip[index]->topBmp);	
	myShip[index]->tempBmp = create_bitmap(topBmp[type]->w, topBmp[type]->h);	
	myShip[index]->topBmp = create_bitmap(topBmp[type]->w, topBmp[type]->h);
		// copy topbmp
	blit(topBmp[type],myShip[index]->topBmp,0,0,0,0,topBmp[type]->w, topBmp[type]->h);
		// ensure ship is drawn properly
	myShip[index]->DrawTemp();

}

/// I am the registraton function. I put all active ships into the
/// crash bins
void ShipCtrl::Register(){
	for(int itor = 0; itor < MAXSHIP; itor++){
			// found active ship, lets register it
		if( myShip[itor]->sinkPhase < myShip[itor]->maxSinkPhase){
			myCrashBin->Register(tpBinType::btBoat, itor, 
				myShip[itor]->center->x, myShip[itor]->center->y);
		}
	}
}

/// I am the update function I run the update function for each ship.
/// I also access the CrashBin and inform the ship of its neighbors
void ShipCtrl::Update(){
	for(int itor = 0; itor < MAXSHIP; itor++){
			// found active ship, lets register it
		if( myShip[itor]->sinkPhase < myShip[itor]->maxSinkPhase){
			UpdateShip(itor);
		}
	}
}

/// update the ship indicated by index
void ShipCtrl::UpdateShip(int index){
	float seekRad = 200;
		// find how many elements we have to work with
	int maxGrid = myCrashBin->CountArea(myShip[index]->center->x,  
		myShip[index]->center->y, seekRad);
		// itorate through elements
	for(int itor =0; itor < maxGrid; itor++){
		tpBinType curType = myCrashBin->FetchType(itor,
			myShip[index]->center->x, myShip[index]->center->y, seekRad);
		int curIndex = myCrashBin->FetchIndex(itor,
			myShip[index]->center->x, myShip[index]->center->y, seekRad);
		switch (curType){
			case tpBinType::btBullet:	// interact with bullet
				myShip[index]->GetHit(myBulletCtrl->myBullet[curIndex]);
			break;
				// interact with ship
			case tpBinType::btBoat:
				if( index != curIndex){	// don't double process ship

				}
			break;
			case tpBinType::btPlayer:	// todo Get Pirate ships to run from player
			break;
			case tpBinType::btPeople:	// floating survivor

			break;
		}
		// update ship itself
		myShip[index]->Update();
	}
}

/// I am the draw function I render all ships that are visable
void ShipCtrl::Draw(Camera * cam){
	for(int itor = 0; itor < MAXSHIP; itor++){
			// found active ship, lets register it
		if( myShip[itor]->sinkPhase < myShip[itor]->maxSinkPhase){
			myShip[itor]->Draw(cam);
		}
	}
}

